/*! \page license
 *
 * Copyright (c) 2011, Blaise Lengrand
 * All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without modification,
 * are permitted provided that the following conditions are met:
 *
 * Redistributions of source code must retain the above copyright notice, this list
 * of conditions and the following disclaimer.
 * Redistributions in binary form must reproduce the above copyright notice, this
 * list of conditions and the following disclaimer in the documentation and/or
 * other materials provided with the distribution.
 * Neither the name of `snWin' nor the names of its contributors may be used to
 * endorse or promote products derived from this software without specific prior
 * written permission.
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
 * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
 * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 *
 */
const twitter_feed = {
  'display_name': "Twitter",
  'author': "Blaise Lengrand",
  'id': "twitter",
  'default_color': "#aaaaff",
  'ep': {
    'connect': twitter_connect,
    'update': twitter_update,
    'previous': twitter_previous,
    'publish': twitter_publish,
    'comment': twitter_comment
  },
  // Extra parameters with their default values (will be saved in the session)
  'session': {
    'token': null,
    'token_secret': null
  },
  'options': {
    // Used to update the comments of an entry
    'merge_if_equal': true,
    // AVoid duplicates (for comment updates sometimes...)
    'compare_entry_content': true
  },
  // 60 seconds is the limit imposed by Twitter
  'update_rate_s': 60,
  'publish_char_limit': 140,
  'comment_char_limit': 140
};

//! Add the feed to the list
feed_available[twitter_feed.id] = twitter_feed;

function twitter_connect(feed_id, context)
{
  // Registers the feed
  feed_register(feed_id, twitter_feed, context);

  feed_log("Connecting", feed_id);

  // If there is no session
  if (!context.token && !context.token_secret)
  {
    if (typeof twitter_oauth_token != "undefined" && typeof twitter_oauth_token_secret != "undefined")
    {
      context.token = twitter_oauth_token;
      context.token_secret = twitter_oauth_token_secret;
    }
    else
    {
      feed_log("No session available, will create one", feed_id);
      var url = "system/pages/social/twitter/login.php";
      feed_iframe(url, "90%", "90%");
      return;
    }
  }

  twitter_access_token_set(feed_id, context);
}

//! Function called once the connection is established
function twitter_access_token_set(feed_id, context)
{
  feed[feed_id].session.token = context.token;
  feed[feed_id].session.token_secret = context.token_secret;

  feed_log("Session acquired `" + context['token'] + "'", feed_id);

  // Close the login window
  feed_prompt_close();
  // Save the session
  feed_connected(feed_id);

  feed_log("Feed connected", feed_id);
}

/*! Converts a date into a twitter ID
 */
function twitter_date_to_id(feed_id, date, start_from_end)
{
  var i = 0;
  if (typeof start_from_end == "Boolean" && start_from_end == true)
  {
    for (i = feed_list.length - 1; i >= 0; i--)
    {
      if (feed_list[i].feed_id != feed_id)
        continue;
      if (feed_list[i].date >= date)
        break;
    }
  }
  else
  {
    for (i = 0; i < feed_list.length; i++)
    {
      if (feed_list[i].feed_id != feed_id)
        continue;
      if (feed_list[i].date <= date)
        break;
    }
  }
  var id = null;
  if (feed_list[i] && feed_list[i].extra && feed_list[i].extra.twitter && feed_list[i].extra.twitter.id)
    id = feed_list[i].extra.twitter.id;
  return id;
}

function twitter_update(feed_id, date)
{
  var params = "&type=update";
  var id = twitter_date_to_id(feed_id, date, false);
  if (id)
    params += "&id=" + escape(id);
  feed_log("Update with ID newer than: ID:" + id);

  twitter_get_feed(feed_id, params);
}

function twitter_previous(feed_id, date)
{
  var params = "&type=previous";
  var id = twitter_date_to_id(feed_id, date, true);
  if (id)
    params += "&id=" + escape(id);
  feed_log("Get previous feed entries older than: ID:" + id);

  twitter_get_feed(feed_id, params);
}

function twitter_publish(feed_id, message)
{
  var params = "&type=publish";
  params += "&message=" + escape(message);
  twitter_post_feed(feed_id, params);
}

function twitter_comment(feed_id, entry, message)
{
  var params = "&type=reply";
  params += "&message=" + escape(message);
  params += "&id=" + escape(entry.extra.twitter.id);
  twitter_post_feed(feed_id, params);
}

function twitter_post_feed(feed_id, params)
{
  var token = feed[feed_id].session.token;
  var token_secret = feed[feed_id].session.token_secret;
  var url = "system/pages/social/twitter/action.php?token=" + escape(token) + "&secret=" + escape(token_secret) + params
  feed_get_json(feed_id, url,
    function success(data) {
      feed_callback(feed_id);
    }
  );
}

function twitter_get_feed(feed_id, params)
{
  var token = feed[feed_id].session.token;
  var token_secret = feed[feed_id].session.token_secret;
  var url = "system/pages/social/twitter/action.php?token=" + escape(token) + "&secret=" + escape(token_secret) + params
  feed_get_json(feed_id, url,
    function success(data) {
      // Test the feed
      if (!feed_id || !feed[feed_id])
        return feed_log("Invalid feed", null, "error");
      // On success
      $.each(data, function(i, item) {
        // Makes sure the entry is valid
        if (!item || typeof(item.date) == "undefined")
          return feed_log("Feed with invalid entry - item: " + item + " - item.date: " + item.date, feed_id, "error");

        // Set default comment
        var reply_to = "";
        if (item.extra && item.extra.twitter && item.extra.twitter.screen_name)
          reply_to += "@" + item.extra.twitter.screen_name;
        // Look for all people references in the feed and add them
        var match = item.message.match(/@[^\s<]+/g);
        var reply_to_extra = "";
        for (i in match)
          if (match[i] != reply_to)
            reply_to_extra += " " + match[i];
        item.extra["comment"] = { 'value': reply_to + reply_to_extra + " " };

        // Check if this is a reply to another message
        if (item.extra && item.extra.twitter && item.extra.twitter.reply_to_id)
        {
          var reply_comment = {
            'id': item.extra.twitter.reply_to_id,
            'extra': {
              'comment': {
                'data': new Array({
                  'name': item.name,
                  'text': item.message.replace(/^(\s*)<a[^>]*>\s*@\w+\s*<\/a\s*>/, "$1"),
                  'date': item.date
                })
              }
            }
          };
          feed_entry_add(reply_comment, feed_id);
        }

        // Add the feed entry
        feed_entry_add(item, feed_id);
      });
      feed_callback(feed_id);
    }
  );
}
